home *** CD-ROM | disk | FTP | other *** search
/ Sprite 1984 - 1993 / Sprite 1984 - 1993.iso / src / kernel / net / netRoute.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-12-19  |  38.1 KB  |  1,375 lines

  1. /* 
  2.  * netRoute.c --
  3.  *
  4.  *    This is the code that maintains a table of routes to
  5.  *    Sprite hosts.  The routes contain the transport level
  6.  *    headers that need to be pre-pended to messages so that
  7.  *    they get to the desired Sprite Host.
  8.  *      Routes are added via a system call or determined dynamically using
  9.  *      Sprite's version of ARP (Address Resolution Protocol).  ARP is
  10.  *      invoked when a call to Net_Output is made with a SpriteID for
  11.  *      which there is no route.  Its use is hidden within Net_Output
  12.  *      should not affect the caller of Net_Output.
  13.  *
  14.  *    Operations on routes are:
  15.  *        Net_InstallRoute - Set the Sprite ID for an ethernet address
  16.  *        Net_AddrToID - Get the Sprite ID for a network address
  17.  *        Net_IDToRoute - Return the route for a Sprite host.
  18.  *    Furthermore, the Test_Stats system call will return a route
  19.  *    to a user program with the NET_GET_ROUTE command.
  20.  *
  21.  * Copyright 1988 Regents of the University of California
  22.  * Permission to use, copy, modify, and distribute this
  23.  * software and its documentation for any purpose and without
  24.  * fee is hereby granted, provided that the above copyright
  25.  * notice appear in all copies.  The University of California
  26.  * makes no representations about the suitability of this
  27.  * software for any purpose.  It is provided "as is" without
  28.  * express or implied warranty.
  29.  *
  30.  */
  31.  
  32. #ifndef lint
  33. static char rcsid[] = "$Header: /cdrom/src/kernel/Cvsroot/kernel/net/netRoute.c,v 9.13 92/06/08 22:49:35 jhh Exp $ SPRITE (Berkeley)";
  34. #endif
  35.  
  36. #include <sprite.h>
  37. #include <net.h>
  38. #include <netRoute.h>
  39. #include <netInt.h>
  40. #include <netUltraInt.h>
  41. #include <sys.h>
  42. #include <stdlib.h>
  43. #include <timer.h>
  44. #include <sync.h>
  45. #include <proc.h>
  46. #include <rpc.h>
  47. #include <string.h>
  48. #include <vm.h>
  49. #include <rpcPacket.h>
  50.  
  51. /*
  52.  * Wildcard address for the Ultranet.  This address matches any address.
  53.  */
  54.  
  55. static Net_UltraTLAddress    wildcardAddress = 
  56.                 {7, NET_ULTRA_TSAP_SIZE};
  57. /*
  58.  * The Route table.
  59.  * The table is indexed by Sprite Host IDs.  Access to
  60.  * the table is synchronized with a MASTER_LOCK to prevent
  61.  * changes from interfering with packet handling.
  62.  */
  63. List_Links    netRouteArray[NET_NUM_SPRITE_HOSTS];
  64. NetHostInfo    netHostInfo[NET_NUM_SPRITE_HOSTS];
  65. int         netNumHosts = NET_NUM_SPRITE_HOSTS;
  66. Sync_Semaphore    netRouteMutex = Sync_SemInitStatic("netRouteMutex");
  67. Sync_Semaphore    netFreeRouteMutex = Sync_SemInitStatic("netFreeRouteMutex");
  68.  
  69. /*
  70.  * Macro to swap the fragOffset field.
  71.  */
  72. #define SWAP_FRAG_OFFSET_HOST_TO_NET(ptr) { \
  73.     unsigned short    *shortPtr; \
  74.     shortPtr = ((unsigned short *)&ptr->ident) + 1; \
  75.     *shortPtr = Net_HostToNetShort(*shortPtr); \
  76.  
  77. static    void        FillUserRoute _ARGS_((Net_Route *routePtr,
  78.                     Net_UserRoute *userRoutePtr));
  79. static    void        FillRouteInfoOld _ARGS_((Net_Route *routePtr,
  80.                     Net_RouteInfoOld *infoPtr));
  81.  
  82. /*
  83.  * This variable is only needed for backwards compatibility with netroute.
  84.  * Once the need for the OLD_NET stuff goes away so can this variable.
  85.  */
  86. static Boolean        oldMode;
  87.  
  88. /*
  89.  *----------------------------------------------------------------------
  90.  *
  91.  * Net_RouteInit --
  92.  *
  93.  *      Initialize the broadcast routes.  The rest of the routes are
  94.  *      installed via the netRoute user program.  
  95.  *
  96.  *    This uses malloc, so it should be called after Mem_Init.
  97.  *
  98.  * Results:
  99.  *    None.
  100.  *
  101.  * Side effects:
  102.  *    Initialize the route table and add the broadcast route.
  103.  *
  104.  *----------------------------------------------------------------------
  105.  */
  106. void
  107. Net_RouteInit()
  108. {
  109.     register int i;
  110.     int spriteID;
  111.  
  112.     /*
  113.      * The route table.  An array of routes is kept for directing
  114.      * messages to other machines.  It is indexed by Sprite host ids.
  115.      */
  116.     for (spriteID=0 ; spriteID<netNumHosts ; spriteID++) {
  117.     List_Init(&netRouteArray[spriteID]);
  118.     bzero((char *) &netHostInfo[spriteID], sizeof(NetHostInfo));
  119.     }
  120.     /*
  121.      * Install the broadcast route(s) so we can do our first broadcast rpcs.
  122.      */
  123.     for (i = 0; i < netNumInterfaces;i++) {
  124.     Net_Interface    *interPtr;
  125.     ReturnStatus    status;
  126.  
  127.     interPtr = netInterfaces[i];
  128.     if (interPtr->flags & NET_IFLAGS_BROADCAST) {
  129.         status = Net_InstallRoute(NET_BROADCAST_HOSTID, 
  130.                 interPtr, &interPtr->broadcastAddress, 
  131.                 NET_PROTO_RAW, "broadcast", "unknown", 
  132.                 0, RPC_MAX_SIZE,
  133.                 (ClientData) 0);
  134.         if (status != SUCCESS) {
  135.         printf(
  136.     "Net_RouteInit: unable to install broadcast route for interface %d\n",
  137.             i);
  138.         }
  139.     }
  140.     }
  141.     return;
  142. }
  143.  
  144. /*
  145.  *----------------------------------------------------------------------
  146.  *
  147.  * Net_InstallRouteStub --    
  148.  *
  149.  *    System call stub for Net_InstallRoute. The Net_RouteInfoOld
  150.  *    stuff is for backwards compatibility and can be removed
  151.  *    once netroute is updated to use Net_UserRoute instead of
  152.  *    Net_RouteInfo.
  153.  *
  154.  * Results:
  155.  *    A return status.
  156.  *
  157.  * Side effects:
  158.  *    See Net_InstallRoute
  159.  *
  160.  *----------------------------------------------------------------------
  161.  */
  162. ReturnStatus
  163. Net_InstallRouteStub(size, userRoutePtr)
  164.     int          size;
  165.     Net_UserRoute *userRoutePtr;    /* Route data */
  166. {
  167.     ReturnStatus     status = SUCCESS;
  168.     Net_Interface     *interPtr;
  169.     Net_UserRoute     userRoute;
  170.  
  171.     if (userRoutePtr == USER_NIL) {
  172.     return (SYS_ARG_NOACCESS);
  173.     }
  174.     /*
  175.      * This stuff allows the new version of Net_Address and Net_UserRoute
  176.      * to work with old applications. 
  177.      */
  178.     if (size == sizeof(Net_RouteInfoOld)) {
  179.     Net_RouteInfoOld    routeInfoOld;
  180.     status = Vm_CopyIn(sizeof(Net_RouteInfoOld), (Address)userRoutePtr, 
  181.               (Address)&routeInfoOld);
  182.     if (status != SUCCESS) {
  183.         return(status);
  184.     }
  185. #define _COPY(field) userRoute.field = routeInfoOld.field
  186.     _COPY(version);
  187.     _COPY(spriteID);
  188.     _COPY(protocol);
  189.     _COPY(flags);
  190.     _COPY(refCount);
  191.     _COPY(routeID);
  192.     _COPY(netType);
  193.     _COPY(userData);
  194.  
  195. #undef _COPY
  196. #define _COPY(field) bcopy(routeInfoOld.field, userRoute.field, sizeof(routeInfoOld.field))
  197.     _COPY(desc);
  198.     _COPY(hostname);
  199.     _COPY(machType);
  200.  
  201. #undef _COPY
  202.     userRoute.minPacket = routeInfoOld.minBytes;
  203.     userRoute.maxPacket = routeInfoOld.maxBytes;
  204.     userRoute.minRpc = 0;
  205.     userRoute.maxRpc = RPC_MAX_SIZE;
  206.     switch(userRoute.netType) {
  207.         case NET_NETWORK_ETHER: 
  208.         status = Net_SetAddress(NET_ADDRESS_ETHER, 
  209.             (Address) &routeInfoOld.netAddress[NET_PROTO_RAW].ether,
  210.             &userRoute.netAddress[NET_PROTO_RAW]);
  211.         break;
  212.         case NET_NETWORK_ULTRA: 
  213.         status = Net_SetAddress(NET_ADDRESS_ULTRA, 
  214.             (Address) &routeInfoOld.netAddress[NET_PROTO_RAW].ultra,
  215.             &userRoute.netAddress[NET_PROTO_RAW]);
  216.         break;
  217.         case NET_NETWORK_FDDI: 
  218.         status = Net_SetAddress(NET_ADDRESS_FDDI, 
  219.             (Address) &routeInfoOld.netAddress[NET_PROTO_RAW].fddi,
  220.             &userRoute.netAddress[NET_PROTO_RAW]);
  221.         break;
  222.     }
  223.     if (status != SUCCESS) {
  224.         panic("Net_InstallRouteStub: Net_SetAddress failed\n");
  225.     }
  226.     if (userRoute.protocol == NET_PROTO_INET) {
  227.         status = Net_SetAddress(NET_ADDRESS_INET, 
  228.         (Address) &routeInfoOld.netAddress[NET_PROTO_INET].inet,
  229.         &userRoute.netAddress[NET_PROTO_INET]);
  230.         if (status != SUCCESS) {
  231.         panic("Net_InstallRouteStub: Net_SetAddress failed\n");
  232.         }
  233.     }
  234.     interPtr = Net_GetInterface(routeInfoOld.netType, 
  235.             routeInfoOld.interface);
  236.     if (interPtr == (Net_Interface *) NIL) {
  237.         printf("Net_InstallRouteStub: can't find interface %d\n",
  238.         routeInfoOld.interface);
  239.         return(GEN_INVALID_ARG);
  240.     }
  241.     userRoute.interAddress = interPtr->netAddress[NET_PROTO_RAW];
  242.     oldMode = TRUE;
  243.     } else if (size == sizeof(Net_UserRoute)) {
  244.     status = Vm_CopyIn(sizeof(Net_UserRoute), (Address)userRoutePtr, 
  245.               (Address)&userRoute);
  246.     if (status != SUCCESS) {
  247.         return(status);
  248.     }
  249.     if (userRoute.version != NET_ROUTE_VERSION) {
  250.         return GEN_INVALID_ARG;
  251.     }
  252.     oldMode = FALSE;
  253.     } else {
  254.     return (GEN_INVALID_ARG);
  255.     }
  256.     interPtr = Net_GetInterfaceByAddr(&userRoute.interAddress);
  257.     if (interPtr == (Net_Interface *) NIL) {
  258.     char    buf[20];
  259.     Net_AddrToString(&userRoute.interAddress, buf);
  260.     printf("Net_InstallRouteStub: can't find interface with address %s\n",
  261.         buf);
  262.     return(GEN_INVALID_ARG);
  263.     }
  264.     status = Net_InstallRoute(userRoute.spriteID,
  265.             interPtr, userRoute.netAddress, 
  266.             userRoute.protocol,
  267.             userRoute.hostname, userRoute.machType, 
  268.             userRoute.minRpc, userRoute.maxRpc,
  269.             userRoute.userData);
  270.     return(status);
  271. }
  272.  
  273. /*
  274.  *----------------------------------------------------------------------
  275.  *
  276.  * Net_InstallRoute --
  277.  *
  278.  *    Install a route to a Sprite host at the specified address.
  279.  *    After installing the route the Sprite ID can be used as an
  280.  *    argument to Rpc_Call to direct an RPC request to that Sprite host.
  281.  *
  282.  * Results:
  283.  *    None.
  284.  *
  285.  * Side effects:
  286.  *    Initialize the entry in the route table which is indexed
  287.  *    by the Sprite ID to point to a route for the Sprite Host.
  288.  *
  289.  *----------------------------------------------------------------------
  290.  */
  291.  
  292. ReturnStatus
  293. Net_InstallRoute(spriteID, interPtr, netAddressPtr, protocol, 
  294.     hostname, machType, minRpc, maxRpc, clientData)
  295.     int         spriteID;    /* Sprite Host ID */
  296.     Net_Interface    *interPtr;    /* Interface route is for. */
  297.     Net_Address     *netAddressPtr;    /* Network addresses (indexed by
  298.                      * protocol). */
  299.     int            protocol;    /* Protocol to use with route. */
  300.     char         *hostname;    /* Human recognizable name */
  301.     char         *machType;      /* Machine type to expand $MACHINE */
  302.     int            minRpc;        /* Minimum RPC size for route. */
  303.     int            maxRpc;        /* Maximum RPC size for route. */
  304.     ClientData        clientData;     /* Data for user-level program. */
  305. {
  306.     register Net_Route     *routePtr;
  307.     Net_Route        *oldRoutePtr = (Net_Route *) NIL;
  308.     ReturnStatus status = SUCCESS;
  309.     char    *headerPtr;
  310.  
  311.     if (Mach_AtInterruptLevel()) {
  312.     printf("Can't install route when at interrupt level (%d)\n",
  313.         spriteID);
  314.     return FAILURE;
  315.     }
  316.     if (spriteID < 0) {
  317.     printf("Invalid sprite id %d\n", spriteID);
  318.     return (GEN_INVALID_ARG);
  319.     }
  320.     /*
  321.      * If we are installing a route and we don't know are own spriteID see
  322.      * if we can learn it from the route.
  323.      */
  324.     if (rpc_SpriteID == 0) {
  325.     if (Net_AddrCmp(&interPtr->netAddress[protocol],
  326.         &netAddressPtr[protocol]) == 0) {
  327.         rpc_SpriteID = spriteID;
  328.     }
  329.     }
  330.     /*
  331.      * If we know our spriteID and we are installing a route to ourselves we
  332.      * can learn (or at least validate our data).
  333.      */
  334.     if ((rpc_SpriteID > 0) && (rpc_SpriteID == spriteID)) {
  335.     char buffer[128];
  336.  
  337.     if (interPtr->netAddress[protocol].type == 0) {
  338.         interPtr->netAddress[protocol] = netAddressPtr[protocol];
  339.         Net_AddrToString(&interPtr->netAddress[protocol], buffer);
  340.         printf("Setting address to %s\n", buffer);
  341.     } else if (Net_AddrCmp(&interPtr->netAddress[protocol], 
  342.             &netAddressPtr[protocol])) {
  343.         Net_AddrToString(&interPtr->netAddress[protocol], buffer);
  344.         printf(
  345.         "Warning: address on interface \"%s\" is currently %s\n",
  346.         interPtr->name,
  347.         buffer);
  348.         Net_AddrToString(&netAddressPtr[protocol], buffer);
  349.         printf("Attempt to install route using address %s ignored.\n",
  350.         buffer);
  351.         status = FAILURE;
  352.     }
  353.     return status;
  354.     }
  355.     routePtr = (Net_Route *) malloc(sizeof(Net_Route));
  356.     MASTER_LOCK(&netRouteMutex);
  357.  
  358.     /*
  359.      * In order to install internet routes our internet address must be set.
  360.      */
  361.     if ((protocol == NET_PROTO_INET) && 
  362.     (!Net_AddrCmp(&interPtr->netAddress[protocol], &netZeroAddress))) {
  363.  
  364.     Boolean     found = FALSE;
  365.     int        addr;
  366.     Net_Route    *tmpPtr;
  367.     /*
  368.      * Try to do a reverse arp to get the internet address.  
  369.      */
  370.     LIST_FORALL(&netRouteArray[NET_BROADCAST_HOSTID], 
  371.         (List_Links *) tmpPtr){
  372.  
  373.         if (tmpPtr->interPtr == interPtr) {
  374.         found = TRUE;
  375.         break;
  376.         }
  377.     }
  378.     if (!found) {
  379.         printf("Can't find broadcast route for interface %s\n",
  380.         interPtr->name);
  381.         MASTER_UNLOCK(&netRouteMutex);
  382.         return FAILURE;
  383.     }
  384.     addr = Net_RevArp(tmpPtr, protocol, (Net_Address *) NIL, 
  385.             &netRouteMutex);
  386.     if (addr == -1) {
  387.         printf("Internet address for interface \"%s\" is not set and\n",
  388.         interPtr->name);
  389.         printf("reverse arp failed.  Can't install route.\n");
  390.         MASTER_UNLOCK(&netRouteMutex);
  391.         return FAILURE;
  392.     }
  393.     interPtr->netAddress[protocol].type = NET_ADDRESS_INET;
  394.     interPtr->netAddress[protocol].address.inet = addr;
  395.     }
  396.     if (spriteID >= NET_NUM_SPRITE_HOSTS) {
  397.     printf("Net route table too small!\n");
  398.     MASTER_UNLOCK(&netRouteMutex);
  399.     return FAILURE;
  400.     } else {
  401.     Net_Route     *tmpPtr;
  402.     if (oldMode) {
  403.         oldRoutePtr = (Net_Route *)NIL;
  404.         LIST_FORALL(&netRouteArray[spriteID], (List_Links *) tmpPtr) {
  405.         if ((tmpPtr->interPtr == interPtr) &&
  406.             (tmpPtr->protocol == protocol)) {
  407.     
  408.             tmpPtr->flags &= ~NET_RFLAGS_VALID;
  409.             oldRoutePtr = tmpPtr;
  410.             break;
  411.         }
  412.         }
  413.     }
  414.     List_InitElement((List_Links *) routePtr);
  415.     List_Insert((List_Links *) routePtr, 
  416.         LIST_ATREAR((List_Links *) &netRouteArray[spriteID]));
  417.     (void) strncpy(netHostInfo[spriteID].name, hostname, 20);
  418.     (void) strncpy(netHostInfo[spriteID].machType, machType, 12);
  419.  
  420.     routePtr->flags = NET_RFLAGS_VALID;
  421.     routePtr->refCount = 0;
  422.     routePtr->spriteID = spriteID;
  423.     routePtr->interPtr = interPtr;
  424.     routePtr->maxPacket = interPtr->maxBytes;
  425.     routePtr->minPacket = interPtr->minBytes;
  426.     routePtr->minRpc = minRpc;
  427.     routePtr->maxRpc = maxRpc;
  428.     routePtr->protocol = protocol;
  429.     routePtr->routeID = (spriteID << 16) | netHostInfo[spriteID].routes++;
  430.     routePtr->userData = clientData;
  431.     (void) sprintf(routePtr->desc, "Route to %s - ", hostname);
  432.     }
  433.     /*
  434.      * Prepare the Route.  This includes the transport header that
  435.      * will be used in messages sent to the Sprite Host.
  436.      */
  437.     headerPtr = (char *) routePtr->buffer;
  438.     switch(interPtr->netType) {
  439.     case NET_NETWORK_ETHER: {
  440.         Net_EtherHdr *etherHdrPtr;
  441.         Net_EtherAddress    etherAddress;
  442.  
  443.         status = Net_GetAddress(&netAddressPtr[NET_PROTO_RAW], 
  444.         (Address) ðerAddress);
  445.         if (status != SUCCESS) {
  446.         panic("Net_InstallRoute: Net_GetAddress failed\n");
  447.         }
  448.         (void) strcat(routePtr->desc, "ethernet, ");
  449.         if (oldMode) {
  450.         /*
  451.          * Fill in an ethernet header for the route.
  452.          * The drivers fill in the source part of the ethernet header 
  453.          * each time they send out a packet.
  454.          */
  455.         if (oldRoutePtr != (Net_Route *) NIL) {
  456.             etherHdrPtr = (Net_EtherHdr *)
  457.                     oldRoutePtr->headerPtr[NET_PROTO_RAW];
  458.             if (Net_EtherAddrCmp(etherAddress,
  459.             NET_ETHER_HDR_DESTINATION(*etherHdrPtr))) {
  460.             char buf[20];
  461.     
  462.             Net_EtherAddrToString(
  463.                 &NET_ETHER_HDR_DESTINATION(*etherHdrPtr), buf);
  464.             printf(
  465.             "Warning: Net_InstallRoute: host <%d> changing ethernet addr\n",
  466.                 spriteID);
  467.             printf("\tOld: %s, ",buf);
  468.             Net_EtherAddrToString(ðerAddress, buf);
  469.             printf("New: %s\n", buf);
  470.             }
  471.         }
  472.         }
  473.         if (protocol == NET_PROTO_RAW) {
  474.         etherHdrPtr = (Net_EtherHdr *)routePtr->buffer;
  475.         NET_ETHER_HDR_TYPE(*etherHdrPtr) = 
  476.             Net_HostToNetShort(NET_ETHER_SPRITE);
  477.         } else {
  478.         /*
  479.          * Make the ethernet header start on an odd 16 bit boundary so
  480.          * that the (internet) header that follows starts on a
  481.          * 32 bit boundary.
  482.          */
  483.         etherHdrPtr = (Net_EtherHdr *)
  484.             ((((int) routePtr->buffer + 5) & ~0x3) - 2);
  485.         NET_ETHER_HDR_TYPE(*etherHdrPtr) = 
  486.                     Net_HostToNetShort(NET_ETHER_IP);
  487.         }
  488.         routePtr->headerPtr[NET_PROTO_RAW] = (Address)etherHdrPtr;
  489.         status = Net_GetAddress(&netAddressPtr[NET_PROTO_RAW],
  490.             (Address) &NET_ETHER_HDR_DESTINATION(*etherHdrPtr));
  491.         if (status != SUCCESS) {
  492.         panic("Net_InstallRoute: Net_GetAddress failed\n");
  493.         }
  494.         status = Net_GetAddress(&interPtr->netAddress[NET_PROTO_RAW],
  495.             (Address) &NET_ETHER_HDR_SOURCE(*etherHdrPtr));
  496.         if (status != SUCCESS) {
  497.         panic("Net_InstallRoute: Net_GetAddress failed\n");
  498.         }
  499.         routePtr->netAddress[NET_PROTO_RAW] = netAddressPtr[NET_PROTO_RAW];
  500.         headerPtr = (char *) etherHdrPtr;
  501.         break;
  502.     }
  503.     case NET_NETWORK_ULTRA: {
  504.         Net_UltraHeader    *ultraHdrPtr;
  505.  
  506.         ultraHdrPtr = (Net_UltraHeader *) routePtr->buffer;
  507.         bzero((char *) ultraHdrPtr, sizeof(Net_UltraHeader));
  508.         (void) strcat(routePtr->desc, "ultranet, ");
  509.         routePtr->headerPtr[NET_PROTO_RAW] = (Address) ultraHdrPtr;
  510.         ultraHdrPtr->remoteAddress = wildcardAddress;
  511.         ultraHdrPtr->remoteAddress.tsapSize=2;
  512.         ultraHdrPtr->remoteAddress.tsap[0]=0xff;
  513.         ultraHdrPtr->remoteAddress.tsap[1]=0xff;
  514.         status = Net_GetAddress(&netAddressPtr[NET_PROTO_RAW], 
  515.         (Address) &ultraHdrPtr->remoteAddress.address);
  516.         if (status != SUCCESS) {
  517.         panic("Net_InstallRoute: Net_GetAddress failed\n");
  518.         }
  519.         ultraHdrPtr->localAddress = wildcardAddress;
  520.         ultraHdrPtr->localAddress.tsapSize=2;
  521.         ultraHdrPtr->localAddress.tsap[0]=0xff;
  522.         ultraHdrPtr->localAddress.tsap[1]=0xff;
  523.         status = Net_GetAddress(&interPtr->netAddress[NET_PROTO_RAW],
  524.         (Address) &ultraHdrPtr->localAddress.address);
  525.         if (status != SUCCESS) {
  526.         panic("Net_InstallRoute: Net_GetAddress failed\n");
  527.         }
  528.         ultraHdrPtr->cmd = NET_ULTRA_DGRAM_SEND_REQ;
  529.         headerPtr = (char *) ultraHdrPtr;
  530.         routePtr->netAddress[NET_PROTO_RAW] = netAddressPtr[NET_PROTO_RAW];
  531.         break;
  532.     }
  533.     case NET_NETWORK_FDDI: {
  534.         Net_FDDIHdr *fddiHdrPtr;
  535.  
  536.         (void) strcat(routePtr->desc, "fddi, ");
  537.         fddiHdrPtr = (Net_FDDIHdr *) routePtr->buffer;
  538.         routePtr->headerPtr[NET_PROTO_RAW] = (Address)fddiHdrPtr;
  539.         bzero((char *) fddiHdrPtr, sizeof(Net_FDDIHdr));
  540.         fddiHdrPtr->frameControl = NET_FDDI_SPRITE;             /***/
  541.         NET_FDDI_ADDR_COPY(netAddressPtr[NET_PROTO_RAW].address.fddi,
  542.                    fddiHdrPtr->dest);
  543.         NET_FDDI_ADDR_COPY(interPtr->netAddress[NET_PROTO_RAW].address.fddi,
  544.                    fddiHdrPtr->source);
  545.         headerPtr = (char *) fddiHdrPtr;
  546.         routePtr->netAddress[NET_PROTO_RAW] = netAddressPtr[NET_PROTO_RAW];
  547.         break;
  548.     }
  549.     default:
  550.         printf("Net_InstallRoute: Unknown interface type %d\n", 
  551.         interPtr->netType);
  552.         return FAILURE;
  553.     }
  554.     headerPtr += net_NetworkHeaderSize[interPtr->netType];
  555.     switch (protocol) {
  556.     case NET_PROTO_RAW:
  557.         (void) strcat(routePtr->desc, "raw");
  558.         break;
  559.     case NET_PROTO_INET: {
  560.         Net_IPHeader *ipHeader;
  561.         (void) strcat(routePtr->desc, "IP");
  562.         ipHeader = (Net_IPHeader *) headerPtr;
  563.         routePtr->headerPtr[protocol] = (Address)ipHeader;
  564.         /*
  565.          * Initialize the template ipHeader.
  566.          */
  567.         bzero((char *)ipHeader, sizeof(Net_IPHeader));
  568.         ipHeader->headerLen = sizeof(Net_IPHeader) / 4;
  569.         ipHeader->version = NET_IP_VERSION;
  570.         ipHeader->typeOfService = 0;
  571.         /*
  572.          * Kernel IP doesn't handle fragmented IP packets (yet).
  573.          */
  574.         ipHeader->flags = NET_IP_DONT_FRAG;
  575.         SWAP_FRAG_OFFSET_HOST_TO_NET(ipHeader);
  576.         ipHeader->timeToLive = NET_IP_MAX_TTL;
  577.         ipHeader->protocol = NET_IP_PROTOCOL_SPRITE;
  578.         status = Net_GetAddress(&interPtr->netAddress[protocol], 
  579.         (Address) &ipHeader->source);
  580.         if (status != SUCCESS) {
  581.         panic("Net_InstallRoute: Net_GetAddress failed\n");
  582.         }
  583.         status = Net_GetAddress(&netAddressPtr[protocol], 
  584.         (Address) &ipHeader->dest);
  585.         if (status != SUCCESS) {
  586.         panic("Net_InstallRoute: Net_GetAddress failed\n");
  587.         }
  588.         /*
  589.          * Precompute the checksum for the ipHeader. This must be
  590.          * corrected when the totalLen field is updated. Note we
  591.          * store the checksum as the 16 bit sum of the packet
  592.          * header to permit easy updating.
  593.          */
  594.         ipHeader->checksum = Net_InetChecksum(sizeof(Net_IPHeader),
  595.                            (Address) ipHeader);
  596.         ipHeader->checksum = ~ipHeader->checksum;
  597.         routePtr->maxPacket -= sizeof(Net_IPHeader);
  598.         routePtr->minPacket -= sizeof(Net_IPHeader);
  599.         if (routePtr->minPacket < 0) {
  600.         routePtr->minPacket = 0;
  601.         }
  602.         routePtr->netAddress[NET_PROTO_INET] = 
  603.         netAddressPtr[NET_PROTO_INET];
  604.         break;
  605.     }
  606.     default: {
  607.         if (oldMode) {
  608.         if (oldRoutePtr != (Net_Route *) NIL) {
  609.             oldRoutePtr->flags |= NET_RFLAGS_VALID;
  610.         }
  611.         }
  612.         printf("Warning: Unsupported route type in Net_InstallRoute\n");
  613.         routePtr->flags &= ~NET_RFLAGS_VALID;
  614.         status = FAILURE;
  615.         break;
  616.     }
  617.     }
  618.     MASTER_UNLOCK(&netRouteMutex);
  619.     if (oldMode) {
  620.     if (oldRoutePtr != (Net_Route *) NIL) {
  621.         Net_DeleteRoute(oldRoutePtr);
  622.     }
  623.     }
  624.     if ((status != SUCCESS) && (routePtr != (Net_Route *) NIL)) {
  625.     Net_DeleteRoute(routePtr);
  626.     }
  627.     return(SUCCESS);
  628. }
  629.  
  630. /*
  631.  *----------------------------------------------------------------------
  632.  *
  633.  * Net_ReleaseRoute --
  634.  *
  635.  *    Releases a route by decrementing its reference count.
  636.  *
  637.  * Results:
  638.  *    None.
  639.  *
  640.  * Side effects:
  641.  *    The route if freed if it is invalid and the reference count is zero.
  642.  *
  643.  *----------------------------------------------------------------------
  644.  */
  645.  
  646. void
  647. Net_ReleaseRoute(routePtr)
  648.     Net_Route     *routePtr;
  649. {
  650.     Boolean     freeIt = FALSE;
  651.     MASTER_LOCK(&netRouteMutex);
  652.     routePtr->refCount--;
  653.     if (Mach_AtInterruptLevel()) {
  654.     goto exit;
  655.     }
  656.     if ((!(routePtr->flags & NET_RFLAGS_VALID)) && 
  657.     (routePtr->refCount <= 0) &&
  658.     (!(routePtr->flags & NET_RFLAGS_DELETING))) {
  659.     routePtr->flags |= NET_RFLAGS_DELETING;
  660.     freeIt = TRUE;
  661.     }
  662. exit:
  663.     MASTER_UNLOCK(&netRouteMutex);
  664.     if (freeIt) {
  665.     List_Remove((List_Links *) routePtr);
  666.     free((char *) routePtr);
  667.     }
  668. }
  669.  
  670. /*
  671.  *----------------------------------------------------------------------
  672.  *
  673.  * Net_DeleteRouteStub --
  674.  *
  675.  *    System call interface for Net_DeleteRoute.
  676.  *
  677.  * Results:
  678.  *    None.
  679.  *
  680.  * Side effects:
  681.  *    None.
  682.  *
  683.  *----------------------------------------------------------------------
  684.  */
  685.  
  686. ReturnStatus
  687. Net_DeleteRouteStub(routeID)
  688.     int        routeID;    /* ID of the route to be deleted. */
  689. {
  690.     int        spriteID;
  691.     Net_Route    *routePtr;
  692.     Boolean    found = FALSE;
  693.  
  694.     spriteID = routeID >> 16;
  695.     if (spriteID < 0 || spriteID >= netNumHosts) {
  696.     return GEN_INVALID_ARG;
  697.     }
  698.     MASTER_LOCK(&netRouteMutex);
  699.     LIST_FORALL(&netRouteArray[spriteID],(List_Links *) routePtr) {
  700.     if (routePtr->routeID == routeID) {
  701.         found = TRUE;
  702.         break;
  703.     }
  704.     }
  705.     MASTER_UNLOCK(&netRouteMutex);
  706.     if (!found) {
  707.     return GEN_INVALID_ARG;
  708.     }
  709.     Net_DeleteRoute(routePtr);
  710.     return SUCCESS;
  711. }
  712.  
  713.  
  714. /*
  715.  *----------------------------------------------------------------------
  716.  *
  717.  * Net_DeleteRoute --
  718.  *
  719.  *    Deletes a route.
  720.  *
  721.  * Results:
  722.  *    A return status.
  723.  *
  724.  * Side effects:
  725.  *    The indicated route is deleted.
  726.  *
  727.  *----------------------------------------------------------------------
  728.  */
  729.  
  730. void
  731. Net_DeleteRoute(routePtr)
  732.     Net_Route    *routePtr;
  733. {
  734.     Boolean     freeIt = FALSE;
  735.     MASTER_LOCK(&netRouteMutex);
  736.     routePtr->flags &= ~NET_RFLAGS_VALID;
  737.     if (Mach_AtInterruptLevel()) {
  738.     goto exit;
  739.     }
  740.     if ((routePtr->refCount <= 0) && 
  741.     (!(routePtr->flags & NET_RFLAGS_DELETING))) {
  742.     routePtr->flags |= NET_RFLAGS_DELETING;
  743.     freeIt = TRUE;
  744.     }
  745. exit:
  746.     MASTER_UNLOCK(&netRouteMutex);
  747.     if (freeIt) {
  748.     List_Remove((List_Links *) routePtr);
  749.     free((char *) routePtr);
  750.     }
  751. }
  752.  
  753. /*
  754.  *----------------------------------------------------------------------
  755.  *
  756.  * Net_IDToRouteOldStub --
  757.  *
  758.  *    Stub for the Test_Stats system call, NET_GET_ROUTE command.
  759.  *    This gets a route and copies it out to user space.
  760.  *    This routine is made obsolete by Net_GetRoutes.
  761.  *
  762.  * Results:
  763.  *    A return status.
  764.  *
  765.  * Side effects:
  766.  *    Copies to user space.
  767.  *
  768.  *----------------------------------------------------------------------
  769.  */
  770. ReturnStatus
  771. Net_IDToRouteOldStub(spriteID, size, argPtr)
  772.     int spriteID;        /* option parameter to Test_Stats */
  773.     int    size;            /* Size of user buffer. */
  774.     Address argPtr;        /* User space buffer to hold route */
  775.  
  776. {
  777. #define MIN(a,b) ((a) < (b) ? (a) : (b))
  778.  
  779.     ReturnStatus status;
  780.     Net_Route *routePtr;
  781.     Net_RouteInfoOld routeInfo;
  782.     int toCopy;
  783.  
  784.     if (spriteID < 0 || spriteID >= netNumHosts) {
  785.     return(SYS_INVALID_ARG);
  786.     }
  787.     routePtr = Net_IDToRoute(spriteID, 0, FALSE, (Sync_Semaphore *) NIL, 0);
  788.     if (routePtr == (Net_Route *)NIL) {
  789.     routeInfo.version = NET_ROUTE_VERSION;
  790.     routeInfo.flags = 0;
  791.     } else {
  792.     FillRouteInfoOld(routePtr, &routeInfo);
  793.     }
  794.     toCopy = MIN(size, sizeof(Net_RouteInfoOld) - sizeof(Net_Header));
  795.     status = Vm_CopyOut(toCopy, (Address)&routeInfo, argPtr);
  796.     if (routePtr == (Net_Route *) NIL) {
  797.     return status;
  798.     }
  799.     if (status == SUCCESS) {
  800.     argPtr += toCopy;
  801.     size -= toCopy;
  802.     toCopy = MIN(size, net_NetworkHeaderSize[routePtr->interPtr->netType]);
  803.     status = Vm_CopyOut(toCopy, 
  804.             (Address)routePtr->headerPtr[NET_PROTO_RAW], 
  805.             argPtr);
  806.     argPtr += toCopy;
  807.     size -= toCopy;
  808.     switch(routePtr->protocol) {
  809.         case NET_PROTO_INET:
  810.         toCopy = MIN(size, sizeof(Net_IPHeader));
  811.         status = Vm_CopyOut(sizeof(Net_IPHeader), 
  812.                  (Address)routePtr->headerPtr[NET_PROTO_INET],
  813.                  argPtr);
  814.         argPtr += toCopy;
  815.         size -= toCopy;
  816.         break;
  817.         default:
  818.         break;
  819.     }
  820.     }
  821.     Net_ReleaseRoute(routePtr);
  822.     return(status);
  823. }
  824.  
  825. /*
  826.  *----------------------------------------------------------------------
  827.  *
  828.  * Net_GetRoutes --
  829.  *
  830.  *    System call to return routes to user-level. If the firstID and
  831.  *    lastID are both -1 then all routes are returned, otherwise
  832.  *    only those routes for hosts with IDs between firstID and
  833.  *    lastID, inclusive, are returned. 
  834.  *
  835.  * Results:
  836.  *    A return status.
  837.  *
  838.  * Side effects:
  839.  *    Copies to user space.
  840.  *
  841.  *----------------------------------------------------------------------
  842.  */
  843. ReturnStatus
  844. Net_GetRoutes(firstID, lastID, infoSize, bufferPtr, buffersUsedPtr)
  845.     int     firstID;        /* ID of first host. */
  846.     int     lastID;            /* ID of last host. */
  847.     int     infoSize;        /* The size of Net_RouteInfo. */
  848.     Address    bufferPtr;        /* Buffer for route info. */
  849.     int        *buffersUsedPtr;    /* Number of buffers used. */
  850. {
  851. #define MIN(a,b) ((a) < (b) ? (a) : (b))
  852.  
  853.     ReturnStatus     status = SUCCESS;
  854.     Net_Route         *routePtr;
  855.     Net_UserRoute    userRoute;
  856.     int            i, j;
  857.     int            size;
  858.     int            count = 0;
  859.  
  860.     if ((firstID < -1) || (firstID >= netNumHosts)) {
  861.     return SYS_INVALID_ARG;
  862.     }
  863.     if ((lastID < -1) || (lastID >= netNumHosts)) {
  864.     return SYS_INVALID_ARG;
  865.     }
  866.     if (lastID < firstID) {
  867.     return SYS_INVALID_ARG;
  868.     }
  869.     if (bufferPtr == USER_NIL) {
  870.     return SYS_ARG_NOACCESS;
  871.     }
  872.     if (firstID == -1) {
  873.     if (lastID != -1) {
  874.         return SYS_INVALID_ARG;
  875.     } else {
  876.         firstID = 0;
  877.         lastID = netNumHosts - 1;
  878.     }
  879.     }
  880.     size = MIN(infoSize, sizeof(Net_UserRoute));
  881.     for (i = firstID; i <= lastID; i++) {
  882.     for (j = 0;; j++) {
  883.         routePtr = Net_IDToRoute(i, j, FALSE, (Sync_Semaphore *) NIL, 0);
  884.         if (routePtr == (Net_Route *) NIL) {
  885.         break;
  886.         }
  887.         FillUserRoute(routePtr, &userRoute);
  888.         Net_ReleaseRoute(routePtr);
  889.         status = Vm_CopyOut(size, (Address)&userRoute, bufferPtr);
  890.         if (status != SUCCESS) {
  891.         goto done;
  892.         }
  893.         bufferPtr += size;
  894.         count++;
  895.     }
  896.     }
  897. done:
  898.     if (buffersUsedPtr != USER_NIL) {
  899.     status = Vm_CopyOut(sizeof(int), (Address) &count, 
  900.         (Address) buffersUsedPtr);
  901.     }
  902.     return(status);
  903. }
  904.  
  905. /*
  906.  *----------------------------------------------------------------------
  907.  *
  908.  * Net_IDToRoute --
  909.  *
  910.  *    Return the route to the host specified by the input sprite id.
  911.  *
  912.  * Results:
  913.  *    A pointer to the route for the host.
  914.  *
  915.  * Side effects:
  916.  *    None.
  917.  *
  918.  *----------------------------------------------------------------------
  919.  */
  920. /*ARGSUSED*/
  921. Net_Route *
  922. Net_IDToRoute(spriteID, index, doArp, mutexPtr, size)
  923.     int     spriteID;    /* Sprite id to find route for. */
  924.     int     index;        /* If >= 0 then the index of the route,
  925.                  * otherwise use the size. */
  926.     Boolean    doArp;        /* Do an arp to find a route? */
  927.     Sync_Semaphore *mutexPtr;    /* Mutex to release when doing arp. */
  928.     int     size;        /* Size of RPC to be sent. */
  929. {
  930.     Net_Route     *routePtr = (Net_Route *) NIL;
  931.     register    Net_Route *tmpPtr;
  932.     int            i;
  933.     ReturnStatus    status;
  934.  
  935.     if (spriteID >= 0 && spriteID < netNumHosts) {
  936.     while (1) {
  937.         i = 0;
  938.         MASTER_LOCK(&netRouteMutex);
  939.         if (index >= 0) {
  940.         LIST_FORALL(&netRouteArray[spriteID],(List_Links *) tmpPtr) {
  941.             if (tmpPtr->flags & NET_RFLAGS_VALID) {
  942.             if (i == index) {
  943.                 routePtr = tmpPtr;
  944.                 break;
  945.             }
  946.             i++;
  947.             }
  948.         }
  949.         } else {
  950.         LIST_FORALL(&netRouteArray[spriteID],(List_Links *) tmpPtr) {
  951.             if ((tmpPtr->minRpc <= size) && (tmpPtr->maxRpc >= size) &&
  952.             (tmpPtr->flags & NET_RFLAGS_VALID)) {
  953.             routePtr = tmpPtr;
  954.             break;
  955.             }
  956.         }
  957.         }
  958.         if (routePtr != (Net_Route *) NIL) {
  959.         routePtr->refCount++;
  960.         }
  961.         MASTER_UNLOCK(&netRouteMutex);
  962.         if (routePtr == (Net_Route *) NIL && doArp) {
  963.         status = Net_Arp(spriteID, mutexPtr);
  964.         if (status != SUCCESS) {
  965.             break;
  966.         }
  967.         doArp = FALSE;
  968.         } else {
  969.         break;
  970.         }
  971.     }
  972.     }
  973.     return(routePtr);
  974. }
  975.  
  976. /*
  977.  *----------------------------------------------------------------------
  978.  *
  979.  * Net_AddrToID --
  980.  *
  981.  *      Determine the Sprite host ID from a network address.  This is
  982.  *      used by a server, or Reverse Arp, to determine a client's Sprite
  983.  *      ID from the client's network address.
  984.  *
  985.  *      This routine scans the route table looking for an address
  986.  *      match with the input address.  
  987.  *
  988.  * Results:
  989.  *      A Sprite hostid for the host at the address.  If the physical
  990.  *      address isn't in the table we return a hostid of -1.
  991.  *
  992.  * Side effects:
  993.  *    None.
  994.  *
  995.  *----------------------------------------------------------------------
  996.  */
  997. int
  998. Net_AddrToID(addressPtr)
  999.     Net_Address    *addressPtr;        /* Physical address */
  1000. {
  1001.     register Net_Route     *routePtr;
  1002.     register int     i;
  1003.     register int     ID = -1;
  1004.     int            protocol;
  1005.  
  1006.     switch(addressPtr->type) {
  1007.     case NET_ADDRESS_INET: 
  1008.         protocol = NET_PROTO_INET;
  1009.         break;
  1010.     default:
  1011.         protocol = NET_PROTO_RAW;
  1012.         break;
  1013.     }
  1014.  
  1015.     MASTER_LOCK(&netRouteMutex);
  1016.  
  1017.     for (i=0 ; i<netNumHosts ; i++) {
  1018.     LIST_FORALL(&netRouteArray[i],(List_Links *) routePtr) {
  1019.         if ((routePtr->protocol == protocol) &&
  1020.         (Net_AddrCmp(&routePtr->netAddress[protocol], 
  1021.             addressPtr) == 0)) {
  1022.         ID = routePtr->spriteID;
  1023.         break;
  1024.         }
  1025.     }
  1026.     }
  1027.     MASTER_UNLOCK(&netRouteMutex);
  1028.     return(ID);
  1029. }
  1030.  
  1031. /*
  1032.  *----------------------------------------------------------------------
  1033.  *
  1034.  * Net_HdrToAddr --
  1035.  *
  1036.  *    Determine the Sprite host ID from a transport header. 
  1037.  *
  1038.  * Results:
  1039.  *    SUCCESS if the Sprite ID was found ok, FAILURE otherwise.
  1040.  *
  1041.  * Side effects:
  1042.  *    None.
  1043.  *
  1044.  *----------------------------------------------------------------------
  1045.  */
  1046.  
  1047. ReturnStatus
  1048. Net_HdrToAddr(netType, protocol, headerPtr, netAddressPtr) 
  1049.     Net_NetworkType    netType;        /* Type of network. */
  1050.     int            protocol;        /* Network protocol. */
  1051.     Address        headerPtr;        /* The transport header. */
  1052.     Net_Address        *netAddressPtr;        /* The network address. */
  1053. {
  1054.     Address         offsetPtr;
  1055.     ReturnStatus    status = SUCCESS;
  1056.  
  1057.     if (protocol == NET_PROTO_RAW) {
  1058.     switch(netType) {
  1059.         case NET_NETWORK_ETHER: {
  1060.         status = Net_SetAddress(NET_ADDRESS_ETHER, 
  1061.             (Address) 
  1062.             &NET_ETHER_HDR_SOURCE(*((Net_EtherHdr *) headerPtr)),
  1063.             netAddressPtr);
  1064.         break;
  1065.         }
  1066.         case NET_NETWORK_ULTRA: {
  1067.         status = Net_SetAddress(NET_ADDRESS_ULTRA, 
  1068.             (Address) &((Net_UltraHeader *) headerPtr)->remoteAddress,
  1069.             netAddressPtr);
  1070.         break;
  1071.         }
  1072.         case NET_NETWORK_FDDI: {
  1073.             status = Net_SetAddress(NET_ADDRESS_FDDI,
  1074.                 (Address) &((Net_FDDIHdr *) headerPtr)->source,
  1075.                 netAddressPtr);
  1076.             break;
  1077.         }
  1078.         default:
  1079.         printf("Net_HdrToAddr: unknown netType %d\n", netType);
  1080.         return FAILURE;
  1081.     }
  1082.     if (status != SUCCESS) {
  1083.         panic("Net_HdrToAddr: Net_SetAddress failed\n");
  1084.     }
  1085.     } else {
  1086.     offsetPtr = headerPtr + net_NetworkHeaderSize[netType];
  1087.     switch(protocol) {
  1088.         case NET_PROTO_INET : {
  1089.         Net_InetAddress    inetAddress;
  1090.         inetAddress = (Net_InetAddress) 
  1091.             Net_NetToHostInt(((Net_IPHeader *) offsetPtr)->dest);
  1092.         status = Net_SetAddress(NET_ADDRESS_INET, 
  1093.             (Address) &inetAddress, netAddressPtr);
  1094.         break;
  1095.         }
  1096.         default:
  1097.         printf("Net_HdrToAddr: unknown protocol %d\n", protocol);
  1098.         return FAILURE;
  1099.     }
  1100.     if (status != SUCCESS) {
  1101.         panic("Net_HdrToAddr: Net_SetAddress failed\n");
  1102.     }
  1103.     }
  1104.     return SUCCESS;
  1105. }
  1106.  
  1107.  
  1108. /*
  1109.  *----------------------------------------------------------------------
  1110.  *
  1111.  * Net_HdrToID --
  1112.  *
  1113.  *      Determine the Sprite host ID from a transport header.  This is
  1114.  *      used by a server to determine a client's Sprite
  1115.  *      ID from the transport header.
  1116.  *
  1117.  *
  1118.  * Results:
  1119.  *      A Sprite hostid for the host at the address.  If the physical
  1120.  *      address isn't in the table we return a hostid of -1.
  1121.  *
  1122.  * Side effects:
  1123.  *    None.
  1124.  *
  1125.  *----------------------------------------------------------------------
  1126.  */
  1127. int
  1128. Net_HdrToID(netType, protocol, headerPtr)
  1129.     Net_NetworkType    netType;
  1130.     int            protocol;
  1131.     Address headerPtr;    /* Transport header. */
  1132. {
  1133.     Net_Address     netAddress;
  1134.     ReturnStatus    status;
  1135.  
  1136.     status = Net_HdrToAddr(netType, protocol, headerPtr, &netAddress);
  1137.     if (status != SUCCESS) {
  1138.     printf("Net_HdrToID: unable to get address from header\n");
  1139.     return -1;
  1140.     }
  1141.     return Net_AddrToID(&netAddress);
  1142. }
  1143.  
  1144.  
  1145. /*
  1146.  *----------------------------------------------------------------------
  1147.  *
  1148.  * Net_HdrDestString --
  1149.  *
  1150.  *    Build a printable message of the destination address from a 
  1151.  *    transport header.
  1152.  *
  1153.  *
  1154.  * Results:
  1155.  *    None.
  1156.  *
  1157.  * Side effects:
  1158.  *    None.
  1159.  *
  1160.  *----------------------------------------------------------------------
  1161.  */
  1162. void
  1163. Net_HdrDestString(netType, protocol, headerPtr, bufferLen, buffer)
  1164.     Net_NetworkType    netType;
  1165.     int            protocol;
  1166.     Address headerPtr;    /* Transport header. */
  1167.     int    bufferLen;    /* Length of buffer. */
  1168.     char *buffer;    /* Destination memory for destination string. */
  1169.  
  1170. {
  1171.     Net_Address     netAddress;
  1172.     static char        tmpBuffer[128];
  1173.     ReturnStatus    status;
  1174.  
  1175.     *buffer = '\0';
  1176.     status = Net_HdrToAddr(netType, protocol, headerPtr, &netAddress);
  1177.     if (status != SUCCESS) {
  1178.     printf("Net_HdrDestString: unable to get address from header\n");
  1179.     return;
  1180.     }
  1181.     Net_AddrToString(&netAddress, tmpBuffer);
  1182.     (void) strncpy(buffer, tmpBuffer, bufferLen-1);
  1183.     return;
  1184. }
  1185.  
  1186.  
  1187. /*
  1188.  *----------------------------------------------------------------------------
  1189.  *
  1190.  * Net_SpriteIDToName --
  1191.  *
  1192.  *    Map from a Sprite ID to a host name.
  1193.  *
  1194.  * Results:
  1195.  *      None.
  1196.  *
  1197.  * Side effects:
  1198.  *      None.
  1199.  *
  1200.  *----------------------------------------------------------------------------
  1201.  */
  1202.  
  1203. void
  1204. Net_SpriteIDToName(spriteID, bufferLen, buffer)
  1205.     int     spriteID;
  1206.     int        bufferLen;
  1207.     char     *buffer;
  1208. {
  1209.     *buffer = '\0';
  1210.     MASTER_LOCK(&netRouteMutex);
  1211.     if (spriteID >= 0 && spriteID < netNumHosts) {
  1212.     (void) strncpy(buffer, netHostInfo[spriteID].name, bufferLen-1);
  1213.     }
  1214.     MASTER_UNLOCK(&netRouteMutex);
  1215.     return;
  1216. }
  1217.  
  1218. /*
  1219.  *----------------------------------------------------------------------------
  1220.  *
  1221.  * Net_SpriteIDToMachType --
  1222.  *
  1223.  *    Map from a Sprite ID to a machine type string.  This string is
  1224.  *    used by the filesystem when expanding $MACHINE in pathnames.
  1225.  *
  1226.  * Results:
  1227.  *      A pointer to a string identifying the machine type, i.e. "sun3".
  1228.  *
  1229.  * Side effects:
  1230.  *      None.
  1231.  *
  1232.  *----------------------------------------------------------------------------
  1233.  */
  1234.  
  1235. void
  1236. Net_SpriteIDToMachType(spriteID, bufferLen, buffer)
  1237.     int     spriteID;
  1238.     int        bufferLen;
  1239.     char    *buffer;
  1240. {
  1241.     *buffer = '\0';
  1242.     MASTER_LOCK(&netRouteMutex);
  1243.     if (spriteID >= 0 && spriteID < netNumHosts) {
  1244.     (void) strncpy(buffer, netHostInfo[spriteID].machType, bufferLen-1);
  1245.     }
  1246.     MASTER_UNLOCK(&netRouteMutex);
  1247.     return;
  1248. }
  1249.  
  1250. /*
  1251.  *----------------------------------------------------------------------
  1252.  *
  1253.  * Net_HostPrint --
  1254.  *
  1255.  *    Print out a statement concerning a host.  This maps to a
  1256.  *    string hostname if possible, and prints out the message.
  1257.  *
  1258.  * Results:
  1259.  *    None.
  1260.  *
  1261.  * Side effects:
  1262.  *    printf.
  1263.  *
  1264.  *----------------------------------------------------------------------
  1265.  */
  1266.  
  1267. void
  1268. Net_HostPrint(spriteID, string)
  1269.     int spriteID;
  1270.     char *string;
  1271. {
  1272.     Sys_HostPrint(spriteID, string);
  1273.     return;
  1274. }
  1275.  
  1276. /*
  1277.  *----------------------------------------------------------------------
  1278.  *
  1279.  * FillUserRoute --
  1280.  *
  1281.  *    Converts from a Net_Route to a Net_UserRoute. Net_UserRoute
  1282.  *     is the structure that is passed to user-level.
  1283.  *
  1284.  * Results:
  1285.  *    None.
  1286.  *
  1287.  * Side effects:
  1288.  *    None.
  1289.  *
  1290.  *----------------------------------------------------------------------
  1291.  */
  1292.  
  1293. static void
  1294. FillUserRoute(routePtr, userRoutePtr)
  1295.     Net_Route        *routePtr;     /* The route structure. */
  1296.     Net_UserRoute    *userRoutePtr;    /* The user version of the route. */
  1297. {
  1298.     int        i;
  1299.  
  1300.     userRoutePtr->version = NET_ROUTE_VERSION;
  1301.     userRoutePtr->spriteID = routePtr->spriteID;
  1302.     userRoutePtr->protocol = routePtr->protocol;
  1303.     userRoutePtr->interAddress = routePtr->interPtr->netAddress[NET_PROTO_RAW];
  1304.     userRoutePtr->netType = routePtr->interPtr->netType;
  1305.     userRoutePtr->refCount = routePtr->refCount;
  1306.     userRoutePtr->routeID = routePtr->routeID;
  1307.     userRoutePtr->flags = routePtr->flags;
  1308.     userRoutePtr->maxPacket = routePtr->maxPacket;
  1309.     userRoutePtr->minPacket = routePtr->minPacket;
  1310.     userRoutePtr->maxRpc = routePtr->maxRpc;
  1311.     userRoutePtr->minRpc = routePtr->minRpc;
  1312.     userRoutePtr->userData = routePtr->userData;
  1313.     for(i = 0; i < NET_MAX_PROTOCOLS; i++) {
  1314.     userRoutePtr->netAddress[i] = routePtr->netAddress[i];
  1315.     }
  1316.     (void) strncpy(userRoutePtr->hostname, 
  1317.             netHostInfo[routePtr->spriteID].name, 20);
  1318.     (void) strncpy(userRoutePtr->machType,
  1319.                netHostInfo[routePtr->spriteID].machType, 12);
  1320.     (void) strncpy(userRoutePtr->desc, routePtr->desc, 64);
  1321. }
  1322.  
  1323. /*
  1324.  *----------------------------------------------------------------------
  1325.  *
  1326.  * FillRouteInfoOld --
  1327.  *
  1328.  *    Converts from a Net_Route to a Net_RouteInfoOld. Net_RouteInfoOld
  1329.  *     is the structure that is passed to user-level.
  1330.  *    This routine is here for backwards compatibility and can
  1331.  *    be removed as soon as Net_IDToRouteStub is gone.
  1332.  *
  1333.  * Results:
  1334.  *    None.
  1335.  *
  1336.  * Side effects:
  1337.  *    None.
  1338.  *
  1339.  *----------------------------------------------------------------------
  1340.  */
  1341.  
  1342. static void
  1343. FillRouteInfoOld(routePtr, infoPtr)
  1344.     Net_Route        *routePtr;     /* The route structure. */
  1345.     Net_RouteInfoOld    *infoPtr;    /* The route info structure. */
  1346. {
  1347.     int            i;
  1348.     ReturnStatus    status;
  1349.  
  1350.     infoPtr->version = NET_ROUTE_VERSION;
  1351.     infoPtr->spriteID = routePtr->spriteID;
  1352.     infoPtr->protocol = routePtr->protocol;
  1353.     infoPtr->interface = routePtr->interPtr->number;
  1354.     infoPtr->netType = routePtr->interPtr->netType;
  1355.     infoPtr->refCount = routePtr->refCount;
  1356.     infoPtr->routeID = routePtr->routeID;
  1357.     infoPtr->flags = routePtr->flags;
  1358.     infoPtr->maxBytes = routePtr->maxPacket;
  1359.     infoPtr->minBytes = routePtr->minPacket;
  1360.     infoPtr->userData = routePtr->userData;
  1361.     for(i = 0; i < NET_MAX_PROTOCOLS; i++) {
  1362.     status = Net_GetAddress(&routePtr->netAddress[i], 
  1363.         (Address) &infoPtr->netAddress[i]);
  1364.     if (status != SUCCESS) {
  1365.         break;
  1366.     }
  1367.     }
  1368.     (void) strncpy(infoPtr->hostname, netHostInfo[routePtr->spriteID].name, 20);
  1369.     (void) strncpy(infoPtr->machType,
  1370.                netHostInfo[routePtr->spriteID].machType, 12);
  1371.     (void) strncpy(infoPtr->desc, routePtr->desc, 64);
  1372. }
  1373.  
  1374.